package com.wksc.framework.impexp.handler.exp;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.sql.SQLException;
import java.util.List;

import com.wksc.framework.impexp.bean.BaseFormatParams;
import com.wksc.framework.impexp.bean.Header;
import com.wksc.framework.impexp.constants.IEConstants;
import com.wksc.framework.impexp.constants.PostfixType;
import com.wksc.framework.impexp.handler.BaseHandler;
import com.wksc.framework.impexp.mode.Mode;
import com.wksc.framework.impexp.pattern.FormatPattern;
import com.wksc.framework.impexp.pattern.INeedRowContent;
import com.wksc.framework.impexp.pattern.PatternFactory;
import com.wksc.framework.impexp.template.ExpTemplate;
import com.wksc.framework.impexp.util.ClassFactory;
import com.wksc.framework.impexp.util.ImpExpTools;
import com.wksc.framework.impexp.writer.Writer;
import jxl.read.biff.BiffException;
import jxl.write.WriteException;

/**
 * <p> Title(文件名): BaseExpHandler.java </p>
 * <p> Description(描述): 此类为所有ModeHandler的父类.
 * ModeHandler类主要作用是为Writer类创建待写入的文件 </p>
 * <p> Copyright(版权): Copyright (c) 2011 </p>
 * <p> Company(公司): 成都四方信息技术有限公司 </p>
 * <p> CreateTime(生成日期)：2011-12-5 下午04:58:50 </p>
 * @author wanglei
 * @version impExp_C13
 */
public abstract class BaseExpHandler extends BaseHandler {
	private static final long serialVersionUID = 8644831253904595965L;
	/**待写入的文件*/
    protected  File file;
    /**导出模板*/
    protected ExpTemplate expTemplate;
    /**是否生成多个文件*/
    protected boolean isMultiFile = false;
    /**实际写文件的writer实例*/
    protected Writer writer;
    /**当前的分页号*/
    protected int curPageNum = 1;
    
    public BaseExpHandler(ExpTemplate expTemplate) throws BiffException, FileNotFoundException, IOException {
    	this.expTemplate = expTemplate;
    	init();
    }
    
    
    /*====================================== 供外部调用的方法 start ===========================================*/
    public BaseExpHandler getHandlerInstance() throws BiffException, FileNotFoundException, IOException{
		return this;
    }
    
	@Override
	public int getLoopTime() throws SQLException {
    	int temp = ClassFactory.getData2FileDao().getTotalPage(expTemplate.getQueryTemplate());
    	if(temp > 1){
    		Mode mode = expTemplate.getExpFileMode();
    		switch (mode) {
				case EXP_TXT:{
					isMultiFile = false;
					break;
				}
				default:{
					isMultiFile = true;
					break;
				}
			}
    	}
    	
        if (temp > IEConstants.EXP_MAX_FILES) {
            return IEConstants.EXP_MAX_FILES;
        } else {
            return temp;
        }
	}

	@Override
	public List<?> getDividedData(int loopCount) throws Exception {
		return ClassFactory.getData2FileDao().getData(loopCount, expTemplate.getQueryTemplate());
	}
	
	/**
     * 方法描述：格式化查询出来的数据
     *
     * @param data 待格式化的全部数据
     * @return 格式化后的全部数据
     * @creator wanglei
     */
	public List<?> formatData(List<?> data){
		//获取写入顺序
        Integer[] order = expTemplate.getWriteOrder();
        //单个表头元素
        Header headerCell;
        //格式化数据pattern
        FormatPattern pattern;
        //格式化参数
        BaseFormatParams formatParams;
        
    	 //强转为以Obejct[]表示的数据集合
        @SuppressWarnings("unchecked")
		List<Object[]> formattedData = (List<Object[]>) data;
        for (Object[] rowCells : formattedData) {
            for (int i = 0; i < order.length; i++) {
            	//如果该单元格内容为空或转换为字符串后为空字符串则直接返回空字符串并继续下次循环
            	if(null == rowCells[order[i]] || (rowCells[order[i]].toString().trim()).equals("")){
            		rowCells[order[i]] = "";
            		continue;
            	}
            	
                headerCell = expTemplate.getFullHeader()[order[i]];

                /* 如果该列数据转换类型或转换pattern不为空则进行格式转换
                 * 若两者都为空则直接转换为字符串
                 */
                if(null != headerCell.getPatternType() || null != headerCell.getPattern()){
                	//如果设置了格式转换类型则从Factory中获取
                	if(null != headerCell.getPatternType()){ 
                		pattern = PatternFactory.getFormatPattern(headerCell.getPatternType());
                	}else{
                		//如果没有设置格式转换类型则表示为自定义格式转换类型
                		pattern = headerCell.getPattern();
                	}
                    
                    //取得格式化参数对象
                    formatParams = expTemplate.getFormatParams();
                	//如果为需要解密的单元格,需要将整列内容设置进参数对象
                	if(pattern instanceof INeedRowContent){
                		formatParams.setLineContent(rowCells); 
                		formatParams.setDecipheringColIndex(order[i]);
                	}
                    //将待格式化单元格的内容对象设置传入格式化参数对象
                    formatParams.setCellContent(rowCells[order[i]]);
                    //格式化单元格内容
                    rowCells[order[i]] = pattern.format(formatParams);
                } else{
					rowCells[order[i]] = rowCells[order[i]].toString().trim();
                }
            }
        }
        
        return formattedData;
    }
	
	/**
     * 将数据写入文件的实际处理方法
	 * @param data 待写入的数据
     * @return 成功写入文件数据的数量(单次)
     */
    public abstract int writeToFile(List<?> data) throws IOException, WriteException, BiffException;
    
    /**
     * 方法描述：是否生成多个文件
     *
     * @creator wanglei
     * @return
     */
    public boolean isMultiFile() {
		return isMultiFile;
	}
    
    /**
	 * 方法描述：获取具体Handler可以处理的文件名后缀
	 *
	 * @creator wanglei
	 * @return
	 */
    public abstract PostfixType getPostfix();
    
    /*==================================== 供外部调用的方法 end ===========================================*/



	/*====================================== 供子类调用的方法 start ===========================================*/
    /**
     * 方法描述：初始化ExpHandler
     * @throws java.io.IOException
     * @throws java.io.FileNotFoundException
     * @throws BiffException 
     *
     * @creator wanglei
     */
    protected abstract void init() throws BiffException, FileNotFoundException,
	IOException;
    
    /**
     * 方法描述：生成文件,主要决定生成路径和文件名
     *
     * @creator wanglei
     * @return
     * @throws java.io.FileNotFoundException
     */
	protected File createFile() throws FileNotFoundException {
		// tempPath为文件生成的绝对路径
		StringBuffer tempPath = new StringBuffer();
		if (isMultiFile) { 
			tempPath.append(
					ImpExpTools.initTempFilePath(expTemplate.getFileName())).append(
					ImpExpTools.initFilename(expTemplate.getFileName(), curPageNum++,
							getPostfix().toString()));
		} else {  // 生成单个文件
			tempPath.append(ImpExpTools.initTempFilePath()).append(
					ImpExpTools.initFilename(expTemplate.getFileName(), getPostfix().toString()));
		}

		return ImpExpTools.getFile(tempPath.toString(), true);
	}
    /*====================================== 供子类调用的方法  end ===========================================*/

}
